//
//  RDConfigServerJsonModel.h
//  RDelivery
//
//  Created by selmerzhang on 2021/8/26.
//  Copyright © 2021 Tencent. All rights reserved.
//
//  协议地址：后台：http://trpc.rick.oa.com/rick/pb/view_protobuf?id=28309
//          Web（Config具体结构）：http://trpc.rick.oa.com/rick/pb/view_protobuf?id=29497

#ifndef RDConfigServerJsonModel_h
#define RDConfigServerJsonModel_h

#import <Foundation/Foundation.h>

//拉取类型
typedef NS_ENUM(NSUInteger, RDConfigServerPullType) {
    RDConfigServerPullTypeUNKNOWN = 0,
    RDConfigServerPullTypeDEPRECATED1 = 1, // 废弃序号，请勿使用
    RDConfigServerPullTypeGROUP = 2,  // 按分组拉取（按sceneid拉取）
    RDConfigServerPullTypeCONFIG = 3, // 按单个配置拉取
    RDConfigServerPullTypeALL = 4,    // 全量拉取
};

//拉取目标
typedef NS_ENUM(NSUInteger, RDConfigServerPullTarget) {
    RDConfigServerPullTargetProject = 0,    // 按项目拉取
    RDConfigServerPullTargetApp = 1, // 按App拉取
};

//平台类型
typedef NS_ENUM(NSUInteger, RDConfigServerPlatform) {
    RDConfigServerPlatformUnknown = 0,
    RDConfigServerPlatformCommon = 1,
    RDConfigServerPlatformAndroid = 2,
    RDConfigServerPlatformIOS = 3,
    RDConfigServerPlatformWeb = 4,
    RDConfigServerPlatformServer = 5,
    RDConfigServerPlatformMicroApp = 6,
    RDConfigServerPlatformIPad = 7,
    RDConfigServerPlatformAndroidPad = 8,
    RDConfigServerPlatformWindows = 9,
    RDConfigServerPlatformMac = 10,
    RDConfigServerPlatformNodeServer = 11,
    RDConfigServerPlatformVisionOS = 12,
    RDConfigServerPlatformHarmony = 13,
};

//状态码
typedef NS_ENUM(NSUInteger, RDConfigServerStatusCode) {
    RDConfigServerStatusCodeSuccess = 0,
    RDConfigServerStatusCodeParamInvalid = 1, // 参数错误
    RDConfigServerStatusCodeServerError = 2, // 系统错误
    RDConfigServerStatusCodeParanIllegal = 3, // 非法请求，如签名错误
    RDConfigServerStatusCodeConfigNotfound = 4, // 配置未找到
    RDConfigServerStatusCodeConfigResultEmpty = 5, // 配置计算结果为空
    RDConfigServerStatusCodeQuotaLimit = 6, // 命中接口限流，SDK在下个周期再拉取，本周期不再重试
    RDConfigServerStatusCodeDomainIllegal = 7, // 请求域名非法，域名与要请求的APPID隔离
    RDConfigServerStatusCodeAddExpCodeExpire = 100, // 扫码添加体验人员：二维码过期
    RDConfigServerStatusCodeAddExpCodeLimit = 101, // 扫码添加体验人员：超出上限
    RDConfigServerStatusCodeAddExpCodeExpNotVip = 102, // 扫码添加体验人员：不在白名单
    RDConfigServerStatusCodeAddExpCodeExpTypeError = 103, // 扫码添加体验人员：类型错误
};

//操作类型
typedef NS_ENUM(NSUInteger, RDConfigServerOpration) {
    RDConfigServerOprationNone = 0, // 保持
    RDConfigServerOprationUpdate = 1, // 更新
    RDConfigServerOprationDelete = 2, // 删除
};

//定义在web协议中
//配置value类型
typedef NS_ENUM(NSUInteger, RDConfigServerValueType) {
    RDConfigServerValueTypeString = 0, // string类型
    RDConfigServerValueTypeJson = 1, // json类型
    RDConfigServerValueTypeInt = 2,
    RDConfigServerValueTypeBool = 3,
    RDConfigServerValueTypeFloat = 4,
    RDConfigServerValueTypeList = 5,
    RDConfigServerValueTypeMap = 6,
};

//定义在web协议中
//配置开关状态
typedef NS_ENUM(NSUInteger, RDConfigSwitchState) {
    RDConfigServerSwitchNone = 0, // 未配置开关
    RDConfigServerSwitchOn = 1, // 开关打开
    RDConfigServerSwitchOff = 2, // 开关关闭
};

//拉取配置类型：开关/配置
typedef NS_ENUM(NSUInteger, RDPullConfigType) {
    RDPullConfigTypeUnknown = 0,
    RDPullConfigTypeConfigSwitch = 1,
    RDPullConfigTypeSwitch = 2,
    RDPullConfigTypeConfig = 3,
};


@class RDServerConfigDetailInfo, RDSystemBizParams, RDSystemBizConfigContent;

NS_ASSUME_NONNULL_BEGIN

#pragma mark - pullConfig协议

// 终端必传属性
@interface RDConfigServerProperties : NSObject
// 平台
@property(nonatomic, assign) RDConfigServerPlatform platform;

// 语言
@property(nonatomic, copy) NSString *language;

// SDK版本号
@property(nonatomic, copy) NSString *sdkVersion;

// 用户id
@property(nonatomic, copy) NSString *guid;

// 宿主App版本号
@property(nonatomic, copy) NSString *appVersion;

// 操作系统版本号
@property(nonatomic, copy) NSString *osVersion;

// bundleId
@property(nonatomic, copy) NSString *bundleId;

// qimei
@property(nonatomic, copy) NSString *qimei;

//是否64位系统
@property(nonatomic, assign) BOOL is64Bit;

//sdk生成的uuid，会序列化到本地，每次请求带的uniqueId一样
@property(nonatomic, copy) NSString *uniqueId;
/// 机型
@property(nonatomic, copy) NSString *manufacturer;
/// 厂商
@property(nonatomic, copy) NSString *model;

@end


// 拉取参数
@interface RDConfigServerPullParams : NSObject
// 多个配置分组，按分组拉取时填写（sceneId）
@property(nonatomic, copy) NSArray<NSNumber *> *groupIDs;
// 配置名，按单个配置拉取时填写
@property(nonatomic, copy) NSString *key;

// 终端必传属性
@property(nonatomic, strong) RDConfigServerProperties *properties;

// 终端自定义属性
@property(nonatomic, copy) NSDictionary *customProperties;

//是否debug包
@property(nonatomic, assign) BOOL isDebugPackage;

// 配置名，按多个配置拉取时填写
@property(nonatomic, copy) NSArray<NSString *> *keys;

@end


#pragma mark - 请求体

// 拉取配置请求
@interface RDConfigServerPullRequest : NSObject
//系统ID
@property(nonatomic, copy) NSString *systemID;

//按AppID拉取时填写
@property(nonatomic, copy) NSString *appID;

// 参数签名，用于校验请求体是否合法，算法参考：https://iwiki.woa.com/pages/viewpage.action?pageId=956353272
@property(nonatomic, copy) NSString *sign;

// 时间戳（秒），用于签名校验
@property(nonatomic, assign) int64_t timestamp;

// 拉取类型
@property(nonatomic, assign) RDConfigServerPullType pullType;

// 拉取参数
@property(nonatomic, strong) RDConfigServerPullParams *pullParams;

// 逻辑环境id
@property(nonatomic, copy) NSString *env;

// 上下文信息，SDK透传
@property(nonatomic, copy) NSString *context;

// 简易的子任务总和校验（如果不一致后台需要重新下发）
@property(nonatomic, copy) NSString *taskChecksum;

// 拉取目标，按项目或按app拉取
@property(nonatomic, assign) RDConfigServerPullTarget target;

// 每个system（Toggle/TAB/...）自身的业务数据
@property(nonatomic, strong) RDSystemBizParams *systemBizParams;

// 拉取配置类型：开关/配置
@property(nonatomic, assign) RDPullConfigType configType;

@end


#pragma mark - Config
@interface Report : NSObject
// 命中的子任务ID
@property(nonatomic, assign) int64_t hitSubTaskID;

@end


@interface RDServerConfigInfo : NSObject
// 配置名称
@property(nonatomic, copy) NSString *key;

// 配置内容JSON值，具体格式SDK与portal进行约定，见http://trpc.rick.oa.com/rick/pb/view_protobuf?id=28805 Config定义
// 收到回包后，需要对value再做一次解析，见RDServerConfigDetailInfo
@property(nonatomic, copy) NSString *value;

// json只会带value字段，需手动从value解出detailInfo对象
@property(nonatomic, strong) RDServerConfigDetailInfo *detailInfo;

// 操作指令：更新/保持/删除
@property(nonatomic, assign) RDConfigServerOpration op;

// 调试信息
@property(nonatomic, copy) NSString *debugInfo;

// 上报信息
@property(nonatomic, strong) Report *report;

// 每个system配置的额外数据
@property(nonatomic, strong) RDSystemBizConfigContent *bizContent;

@end


#pragma mark - 回包


@interface RDConfigServerPullResponse : NSObject
// 错误码
@property(nonatomic, assign) RDConfigServerStatusCode code;

// 错误信息
@property(nonatomic, copy) NSString *msg;

// 下发的配置
@property(nonatomic, copy) NSArray<RDServerConfigInfo *> *configs;

// 上下文信息，SDK透传
@property(nonatomic, copy) NSString *context;

// 下一次拉取最小时间间隔，0使用SDK自身设置的间隔
@property(nonatomic, assign) uint32_t interval;

// 每个system的额外数据
// bizData中按key存放了每个系统的额外数据，key的定义见http://trpc.rick.oa.com/rick/pb/view_protobuf?id=28309 协议中的SystemBizData类型
@property(nonatomic, strong) NSDictionary<NSString *, NSDictionary *> *bizData;

// 是否还有下一分组
@property(nonatomic, assign) BOOL hasNext;

//命中任务情况的标签，用于监控联动圈定人群
@property(nonatomic, copy) NSArray<NSString *> *hitSubTaskTag;

//灯塔sdk采样率， 如: 10,代表十分之一 10000,代表万分之一
@property(nonatomic, assign) uint32_t sampling;

//软限制,下一次拉取最小时间间隔（单位：秒），0使用SDK自身设置的间隔。软限制仅限制自动全量拉取配置
@property(nonatomic, assign) uint32_t softInterval;

//硬限制,下一次拉取最小时间间隔（单位：秒），0使用SDK自身设置的间隔。硬限制限制所有类型的配置拉取
@property(nonatomic, assign) uint32_t hardInterval;

/// 配置变更生效上报标记位：默认false：不上报（后期大部分情况要求不上报）；true,
@property (nonatomic, assign) BOOL isCfgChangeReport;

/// 服务端linux时间戳（毫秒）
@property(nonatomic, assign) uint64_t serverTime;

/// 默认 NO，不关闭上报，YES 关闭上报
@property(nonatomic, assign) BOOL closeBuglyReport;

/// 是否强制覆盖本地配置
@property(nonatomic, assign) BOOL isOverwrite;

/// Rightly 全量上报标识位
@property(nonatomic, assign) BOOL isRightlyFullReport;

@end



//配置具体内容
//定义在web协议中
@interface RDServerConfigDetailInfo : NSObject
//配置类型
@property(nonatomic, assign) RDConfigServerValueType config_value_type;

//配置内容
@property(nonatomic, copy) NSString *config_value;

//配置开关状态
@property(nonatomic, assign) RDConfigSwitchState switch_state;

@end


#pragma mark - TAB业务相关兼容
@interface RDeliveryTABBizParams : NSObject
//TAB的SDK版本号
@property(nonatomic, copy) NSString *sdk_version;

// 透传给模型服务的参数,一般不需要填
@property(nonatomic, copy) NSDictionary<NSString *, NSString *> *model_server_params;

// tab平台额外的参数,目前只支持new_id属性. 启用qimei36则需要填入new_id=xxx
@property(nonatomic, copy) NSDictionary<NSString *, NSString *> *extra_params;

// 是否是第一次请求
@property(nonatomic, assign) BOOL isInitRequest;

@end


@interface RDSystemBizParams : NSObject
// TAB业务请求数据
@property(nonatomic, strong) RDeliveryTABBizParams *tabBizParams;

@end


@interface RDeliveryTABConfigContent : NSObject
// 命中的实验信息，由GrayPolicyInfo JSON序列化得到。如果expData=""为未命中实验。
@property(nonatomic, copy) NSString *expData;

//TAB配置条件ID
@property(nonatomic, assign) int64_t conditionID;

@end


@interface RDSystemBizConfigContent : NSObject
// 命中的实验信息  , 如果是nil 则认为是不命中实验
@property(nonatomic, strong) RDeliveryTABConfigContent *tab;

@end


@interface RDGrayPolicyInfo : NSObject
// 实验ID
@property(nonatomic, assign) int32_t sGrayPolicyId;

// 命中桶号
@property(nonatomic, assign) int32_t bucket;

// 实验比率
@property(nonatomic, assign) float percentage;

// 实验参数
@property(nonatomic, copy) NSDictionary<NSString *, NSString *> *params;

// 实验版本key
@property(nonatomic, copy) NSString *assignment;

// 实验ID
@property(nonatomic, copy) NSString *expName;

// 层桶数
@property(nonatomic, assign) int32_t moduleBuckets;

@end

#pragma mark - 加密请求协议

@interface RDEncryptRequest : NSObject
/// 请求密文（加密后的请求包）
@property(nonatomic, copy) NSString *cipher_text;
/// 调试信息
@property(nonatomic, copy) NSString *debug_info;
/// 公钥版本
@property(nonatomic, assign) int64_t public_key_version;
/// 加密后的对称密钥
@property(nonatomic, copy) NSString *pull_key;
@end

@interface RDEncryptResponse : NSObject
/// 响应密文（加密后的PullResponse）
@property(nonatomic, copy) NSString *cipher_text;
/// 错误码
@property(nonatomic, assign) uint32_t ret_code;
/// 错误信息
@property(nonatomic, copy) NSString *ret_msg;

@end


#pragma mark - GetConfig协议

@interface RDConfigServerGetRequest : NSObject
//系统ID
@property(nonatomic, copy) NSString *systemID;

//按AppID拉取时填写
@property(nonatomic, copy) NSString *appID;

// 参数签名，用于校验请求体是否合法，算法参考：https://iwiki.woa.com/pages/viewpage.action?pageId=956353272 ，步骤3按照systemID、appID、timestamp、appkey的顺序拼接
@property(nonatomic, copy) NSString *sign;

// 时间戳（秒），用于签名校验
@property(nonatomic, assign) int64_t timestamp;

// 任务ID
@property(nonatomic, copy) NSArray<NSNumber *> *taskIDs;

// 拉取目标，按项目或按app拉取
@property(nonatomic, assign) RDConfigServerPullTarget target;

// 用户id
@property(nonatomic, copy) NSString *guid;

//是否debug包
@property(nonatomic, assign) BOOL isDebugPackage;

@end

@interface RDConfigServerGetResponse : NSObject
// 错误码
@property(nonatomic, assign) RDConfigServerStatusCode code;

// 错误信息
@property(nonatomic, copy) NSString *msg;

// 任务ID与对应的配置(这里不填Config.OP与Config.Report)
@property(nonatomic, copy) NSDictionary<NSNumber *, RDServerConfigInfo *> *taskIDConfig;

@end

#pragma mark - GetSDKConfig协议

@interface RDSDKConfigServerGetConfigRequest : NSObject
// 系统ID
@property(nonatomic, copy) NSString *systemID;
// 按AppID拉取时填写
@property(nonatomic, copy) NSString *appID;
// 拉取目标，按项目或按app拉取
@property(nonatomic, assign) RDConfigServerPlatform platform;
// app 版本
@property(nonatomic, copy) NSString *appVersion;
// 设备 qimei
@property(nonatomic, copy) NSString *qimei;
// 唯一 id
@property(nonatomic, copy) NSString *uniqueId;

@end

@interface RDSDKConfigData : NSObject
// TAB 灰度开关
@property(nonatomic, assign) BOOL tabGray;
// TAB 对账开关
@property(nonatomic, assign) BOOL tabDataCheck;

@end

@interface RDSDKConfigServerGetResponse : NSObject
// 错误码
@property(nonatomic, assign) RDConfigServerStatusCode code;
// 错误信息
@property(nonatomic, copy) NSString *msg;

@property (nonatomic, strong) RDSDKConfigData *data;

@end

#pragma mark - 聚合请求协议

// V4 批量拉取配置请求
@interface RDConfigServerBatchPullRequest : NSObject

@property (nonatomic, strong) NSArray<RDEncryptRequest *> *reqList;

@end

// V4 批量拉取配置响应
@interface RDConfigServerBatchPullResponse : NSObject

@property (nonatomic, strong) NSDictionary<NSString *, NSDictionary *> *rspDic;
@property (nonatomic, assign) BOOL notBatchMerge;

@end

#pragma mark - 扫码添加体验用户协议

@interface RDAddExpListRequest : NSObject

/// 按AppID拉取时填写
@property(nonatomic, copy) NSString *appID;
/// 系统ID
@property(nonatomic, copy) NSString *systemID;
/// 拉取目标，按项目或按app拉取
@property(nonatomic, assign) RDConfigServerPullTarget target;
/// 参数签名
@property(nonatomic, copy) NSString *sign;
/// 时间戳（秒），用于签名校验
@property(nonatomic, assign) int64_t timestamp;
/// 二维码ID，扫码后获取
@property(nonatomic, copy) NSString *QRCodeID;
/// 体验id类型，如：guid、qimei内置字段或qq等自定义属性，与体验号码字段类型对齐
@property(nonatomic, copy) NSString *IDType;
/// 体验id
@property(nonatomic, copy) NSString *IDValue;
/// 环境（正式、测试）
@property(nonatomic, copy) NSString *envID;

@end

@interface RDAddExpListResponse : NSObject
// 错误码
@property(nonatomic, assign) RDConfigServerStatusCode code;
// 错误信息
@property(nonatomic, copy) NSString *msg;
@end

NS_ASSUME_NONNULL_END

#endif /* RDConfigServerJsonModel_h */
